package com.haixiaoke.saas.user.service.impl;

import java.util.Date;
import java.util.List;

import cn.binarywang.wx.miniapp.api.WxMaService;
import cn.binarywang.wx.miniapp.bean.WxMaJscode2SessionResult;
import cn.binarywang.wx.miniapp.bean.WxMaPhoneNumberInfo;
import cn.hutool.core.lang.Validator;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson2.JSONObject;
import com.haixiaoke.saas.common.exception.ServiceException;
import com.haixiaoke.saas.common.utils.DateUtils;
import com.haixiaoke.saas.common.weChat.domain.WeChatLoginParam;
import com.haixiaoke.saas.common.weChat.service.WeChatService;
import com.haixiaoke.saas.system.domain.LoginBody;
import com.haixiaoke.saas.system.framework.web.service.SysLoginService;
import com.haixiaoke.saas.user.domain.UserConsumer;
import com.haixiaoke.saas.user.mapper.UserConsumerMapper;
import com.haixiaoke.saas.user.service.IUserConsumerService;
import lombok.extern.slf4j.Slf4j;
import me.chanjar.weixin.common.error.WxErrorException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

/**
 * C端用户Service业务层处理
 * 
 * @author panda
 * @date 2025-07-01
 */
@Slf4j
@Service
public class UserConsumerServiceImpl implements IUserConsumerService {
    @Autowired
    private UserConsumerMapper userConsumerMapper;
    @Autowired
    private WxMaService wxMaService;
    @Autowired
    private SysLoginService sysLoginService;
    @Autowired
    private WeChatService weChatService;

    /**
     * 查询C端用户
     * 
     * @param userId C端用户主键
     * @return C端用户
     */
    @Override
    public UserConsumer selectUserConsumerByUserId(Long userId) {
        return userConsumerMapper.selectUserConsumerByUserId(userId);
    }

    /**
     * 查询C端用户列表
     * 
     * @param userConsumer C端用户
     * @return C端用户
     */
    @Override
    public List<UserConsumer> selectUserConsumerList(UserConsumer userConsumer) {
        return userConsumerMapper.selectUserConsumerList(userConsumer);
    }

    /**
     * 新增C端用户
     * 
     * @param userConsumer C端用户
     * @return 结果
     */
    @Override
    public int insertUserConsumer(UserConsumer userConsumer) {
        userConsumer.setCreateTime(DateUtils.getNowDate());
        return userConsumerMapper.insertUserConsumer(userConsumer);
    }

    /**
     * 修改C端用户
     * 
     * @param userConsumer C端用户
     * @return 结果
     */
    @Override
    public int updateUserConsumer(UserConsumer userConsumer) {
        userConsumer.setUpdateTime(DateUtils.getNowDate());
        return userConsumerMapper.updateUserConsumer(userConsumer);
    }

    /**
     * 批量删除C端用户
     * 
     * @param userIds 需要删除的C端用户主键
     * @return 结果
     */
    @Override
    public int deleteUserConsumerByUserIds(Long[] userIds) {
        return userConsumerMapper.deleteUserConsumerByUserIds(userIds);
    }

    /**
     * 删除C端用户信息
     * 
     * @param userId C端用户主键
     * @return 结果
     */
    @Override
    public int deleteUserConsumerByUserId(Long userId) {
        return userConsumerMapper.deleteUserConsumerByUserId(userId);
    }

    @Override
    public UserConsumer selectUserConsumerByPhone(String userPhone) {
        return userConsumerMapper.selectUserConsumerByPhone(userPhone);
    }

    @Override
    public List<UserConsumer> selectUserByPhoneList(List<String> phoneList) {
        return userConsumerMapper.selectUserByPhoneList(phoneList);
    }

    @Override
    @Transactional
    public UserConsumer weChatSelectUserByPhone(WeChatLoginParam loginParam) {
        String code = loginParam.getCode();
        String encryptedData = loginParam.getEncryptedData();
        String iv = loginParam.getIv();

        WxMaJscode2SessionResult session;
        try {
            session = wxMaService.getUserService().getSessionInfo(code);
        } catch (WxErrorException e) {
            throw new ServiceException("登录异常：" + e.getLocalizedMessage());
        }
        String openid = session.getOpenid();

        String sessionKey = session.getSessionKey();
        WxMaPhoneNumberInfo phoneNoInfo;
        try {
            phoneNoInfo = wxMaService.getUserService().getPhoneNoInfo(sessionKey, encryptedData, iv);
        } catch (Exception e) {
            log.error("数据映射异常:{},{},{}", code, encryptedData, iv, e);
            throw new ServiceException("登录异常,请重新登录");
        }
        String phoneNumber = phoneNoInfo.getPhoneNumber();
        if (StrUtil.isBlank(phoneNumber)) {
            throw new ServiceException("手机号码为空");
        }
        UserConsumer user = userConsumerMapper.selectUserConsumerByPhone(phoneNumber);
        Date nowDate = DateUtils.getNowDate();
        if (ObjectUtil.isEmpty(user)) {
            UserConsumer newUser = new UserConsumer();
            newUser.setUserPhone(phoneNumber);
            newUser.setNickName("未命名");
            newUser.setOpenId(openid);
            newUser.setCreateTime(nowDate);
            newUser.setLastLoginTime(nowDate);
            userConsumerMapper.insertUserConsumer(newUser);
            return newUser;
        } else {
            user.setOpenId(openid);
            user.setUpdateTime(nowDate);
            user.setLastLoginTime(nowDate);
            userConsumerMapper.updateUserConsumer(user);
            return user;
        }
    }

    @Override
    @Transactional
    public UserConsumer selectUserByCaptcha(LoginBody loginBody) {
        String phone = loginBody.getPhonenumber();
        checkParameter(phone);
        // 验证码校验
        sysLoginService.validateMobileCaptcha(phone, loginBody.getCode(), true);
        String openid = null;
        if (StrUtil.isNotBlank(loginBody.getJsCode())) {
            JSONObject jsonObject = weChatService.wechatLogin(loginBody.getJsCode());
            if (jsonObject == null || StrUtil.isNotBlank(jsonObject.getString("errmsg"))) {
                throw new ServiceException("微信登录失败");
            }
            openid = jsonObject.getString("openid");
        }
        UserConsumer user = userConsumerMapper.selectUserConsumerByPhone(phone);
        Date nowDate = DateUtils.getNowDate();
        if (ObjectUtil.isEmpty(user)) {
            UserConsumer newUser = new UserConsumer();
            newUser.setUserPhone(phone);
            newUser.setOpenId(openid);
            newUser.setNickName("未命名");
            newUser.setCreateTime(nowDate);
            newUser.setLastLoginTime(nowDate);
            userConsumerMapper.insertUserConsumer(newUser);
            return newUser;
        } else {
            user.setOpenId(openid);
            user.setLastLoginTime(nowDate);
            userConsumerMapper.updateUserConsumer(user);
            return user;
        }
    }

    private void checkParameter(String phone) {
        if (StrUtil.isEmpty(phone)) {
            throw new ServiceException("手机号不能为空");
        }
        if (!Validator.isMobile(phone)) {
            throw new ServiceException("手机号格式不正确");
        }

    }
}
